package test;

import java.io.InputStream;
import java.io.RandomAccessFile;
import java.net.HttpURLConnection;
import java.net.URL;

/**
 * 多线程下载
 * 
 * @author chao
 * 
 */
public class MutilDownLoader1 {

	private static String path = "http://localhost:9999/feiq.exe";
	/**
	 * 几个线程去下载服务端资源
	 */
	private static int threadCount = 5;

	public static void main(String[] args) {
		try {
			// 声明Url
			URL url = new URL(path);
			// 建立连接
			HttpURLConnection conn = (HttpURLConnection) url.openConnection();
			conn.setConnectTimeout(5000);
			conn.setRequestMethod("GET");
			// 获取返回状态
			int code = conn.getResponseCode();
			if (200 == code) {
				// 获取输入流
				InputStream is = conn.getInputStream();
				// 拿到服务端资源的总大小
				int fileLenth = conn.getContentLength();
				System.out.println("fileLenth:" + fileLenth);
				// 在客户端创建一个和服务端资源一样大小的空文件
				RandomAccessFile raf = new RandomAccessFile(getFileName(), "rw");
				//设置文件的大小
				raf.setLength(fileLenth);
				raf.close();
				// 每个线程下载的区块大小
				int blockSize = fileLenth / threadCount;
				//分别创建线程去下载
				for (int threadId = 0; threadId < threadCount; threadId++) {
					int startIndex = threadId * blockSize;
					int endIndex = (threadId + 1) * blockSize - 1;
					// 最后一个线程修正下载文件的结束位置
					if (threadId == threadCount - 1) {
						endIndex = fileLenth - 1;
					}
					new DownLoaderThread(startIndex, endIndex, threadId)
							.start();
				}
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	static class DownLoaderThread extends Thread {
		// 开始位置
		int startIndex;
		// 结束位置
		int endIndex;
		// 线程ID
		int threadId;

		public DownLoaderThread(int startIndex, int endIndex, int threadId) {
			super();
			this.startIndex = startIndex;
			this.endIndex = endIndex;
			this.threadId = threadId;
		}

		@Override
		public void run() {
			super.run();
			System.out.println("线程：" + threadId + " =" + startIndex + "~~"
					+ endIndex);
			// System.out.println("线程："+threadId+"工作量="+(endIndex-startIndex));
			try {
				URL url = new URL(path);
				HttpURLConnection conn = (HttpURLConnection) url
						.openConnection();
				conn.setConnectTimeout(5000);
				conn.setRequestMethod("GET");
				// 重要，每一个线程请求一段数据
				conn.setRequestProperty("Range", "bytes=" + startIndex + "-"+ endIndex);
				// 2xxx 请求成功 206部分数据完成请求
				int code = conn.getResponseCode();
				System.out.println("code=" + code);
				if (206 == code) {
					// 输入流
					InputStream is = conn.getInputStream();
					// 硬盘上的文件
					RandomAccessFile raf = new RandomAccessFile(getFileName(),"rwd");
					//重要，设置位置
					raf.seek(startIndex);
					
					byte[] buffer = new byte[1024*1024*10];
					int len = 0;
					while ((len = is.read(buffer)) != -1) {
						raf.write(buffer,0,len);
					}
					raf.close();
					is.close();
					System.out.println("线程" + threadId + "干完活了！");
				}

			} catch (Exception e) {
				e.printStackTrace();
			}

		}

	}

	static String getFileName() {
		int index = path.lastIndexOf("/") + 1;
		return path.substring(index);
	}

}
